package com.yumeng.framework.core.mvc;

import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.SneakyThrows;
import org.springframework.boot.autoconfigure.web.ErrorProperties;
import org.springframework.boot.autoconfigure.web.servlet.error.BasicErrorController;
import org.springframework.boot.autoconfigure.web.servlet.error.ErrorViewResolver;
import org.springframework.boot.web.servlet.error.ErrorAttributes;
import org.springframework.http.ResponseEntity;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.util.WebUtils;

import java.util.List;
import java.util.Map;

/**
 * 全局异常处理，非springmvc引发的异常
 * 如filter中的异常
 *
 * @author wxd
 * @date 2024/6/7 下午3:58
 */
public class GlobalErrorController extends BasicErrorController {

    public GlobalErrorController(ErrorAttributes errorAttributes, ErrorProperties errorProperties) {
        super(errorAttributes, errorProperties);
    }

    public GlobalErrorController(ErrorAttributes errorAttributes, ErrorProperties errorProperties, List<ErrorViewResolver> errorViewResolvers) {
        super(errorAttributes, errorProperties, errorViewResolvers);
    }

    @SneakyThrows
    @Override
    public ResponseEntity<Map<String, Object>> error(HttpServletRequest request) {
        if (request.getAttribute(WebUtils.ERROR_EXCEPTION_ATTRIBUTE) != null) {
            Throwable e = (Throwable) request.getAttribute(WebUtils.ERROR_EXCEPTION_ATTRIBUTE);
            if (e.getCause() != null){
                //优先抛出实际异常
                throw e.getCause();
            }else{
                throw e;
            }
        }
        return super.error(request);
    }

    @SneakyThrows
    @Override
    public ModelAndView errorHtml(HttpServletRequest request, HttpServletResponse response) {
        if (request.getAttribute(WebUtils.ERROR_EXCEPTION_ATTRIBUTE) != null) {
            throw (Throwable) request.getAttribute(WebUtils.ERROR_EXCEPTION_ATTRIBUTE);
        }
        return super.errorHtml(request, response);
    }
}
